import org.antlr.v4.runtime.ParserRuleContext;
import org.antlr.v4.runtime.Token;
import org.antlr.v4.runtime.tree.ParseTreeProperty;

public class DefPhase extends CymbolBaseListener{

    ParseTreeProperty<Scope> scopes = new ParseTreeProperty<Scope>();
    GlobalScope global;
    Scope currentScope;
    public void saveScope(ParserRuleContext ctx, Scope scope) {this.scopes.put(ctx, scope);}
    public void defineVar(CymbolParser.TypeContext ctx, Token nameToken) {
        int typeTokenType = ctx.start.getType();
        Symbol.Type type = CheckSymbols.getType(typeTokenType);
        VariableSymbol var = new VariableSymbol(nameToken.getText(), type);
        this.currentScope.define(var);
    }
    public void enterFile(CymbolParser.FileContext ctx) {
        this.global = new GlobalScope(null);
        this.currentScope = this.global;
    }
    public void exitFile(CymbolParser.FileContext ctx) {
        System.out.println(global);
    }
    public void enterFunctionDecl(CymbolParser.FunctionDeclContext ctx) {
        String name = ctx.ID().getText();
        int typeTokenType = ctx.type().start.getType();
        Symbol.Type type = CheckSymbols.getType(typeTokenType);

        FunctionSymbol function = new FunctionSymbol(name, type, this.currentScope);
        this.currentScope.define(function);
        saveScope(ctx, function);
        this.currentScope = function;
    }
    public void exitFunctionDecl(CymbolParser.FunctionDeclContext ctx) {
        System.out.println(this.currentScope);
        this.currentScope = this.currentScope.getEnclosingScope();
    }
    public void enterBlock(CymbolParser.BlockContext ctx) {
        this.currentScope = new LocalScope(this.currentScope);
        saveScope(ctx, this.currentScope);
    }
    public void exitBlock(CymbolParser.BlockContext ctx) {
        System.out.println(this.currentScope);
        this.currentScope = this.currentScope.getEnclosingScope();
    }
    public void exitFormalParameter(CymbolParser.FormalParameterContext ctx) {
        defineVar(ctx.type(), ctx.ID().getSymbol());
    }
    public void exitVarDecl(CymbolParser.VarDeclContext ctx) {
        defineVar(ctx.type(), ctx.ID().getSymbol());
    }


}
